package com.ysw.rpc.server.config;

import com.ysw.rpc.server.handler.initializer.ServerInitializerHandler;
import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.Channel;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelOption;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import lombok.extern.slf4j.Slf4j;

import java.util.concurrent.Executor;

/**
 * @author YinShangwen
 * @since 2023/4/18 10:15
 */
@Slf4j
public class ServerInitializerConfig extends AbstractServerInitializerConfig {
    private final ServerProperties properties;
    private final Executor executor;

    public ServerInitializerConfig(ServerProperties properties, Executor executor) {
        this.properties = properties;
        this.executor = executor;
    }

    @Override
    public void initServer() {
        ServerBootstrap serverBootstrap = new ServerBootstrap()
                .option(ChannelOption.SO_BACKLOG, 1024)
                .childOption(ChannelOption.TCP_NODELAY, true)
                .group(getParent(), getWorker())
                .channel(NioServerSocketChannel.class)
                .childHandler(new ServerInitializerHandler(properties, executor));
        try {
            ChannelFuture channelFuture = serverBootstrap.bind(properties.getPort());
            channelFuture.addListener(future -> {
                if (!future.isSuccess()) {
                    log.info("bind error:", future.cause());
                    closeEventLoopGroup();
                }
            });
            Channel channel = channelFuture.sync().channel();
            channel.closeFuture().addListener(future -> closeEventLoopGroup());
            setChannel(channel);
            log.info("rpc server ok...");
        } catch (Exception e) {
            log.error("rpc server error: ", e);
            closeEventLoopGroup();
        }
    }
}
